package com;

import javax.swing.*;
import java.awt.*;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.io.File;
import java.util.Vector;

/**
 * @author 吴宇~
 * @motto 我亦无他，唯手熟尔。
 * @edition jdk1.8
 * @reflection 0-1 喧闹任其喧闹，自由我自为之，我自风情万种，与世无争。
 * @person Han Xiaojiu
 */

public class MyPanel extends JPanel implements KeyListener, Runnable {
    Hero hero = null;
    Vector<EnemyTank> enemyTanks = new Vector<>();
    //定义一个存放敌人坦克的坐标和方向
    Vector<Node> nodes = new Vector<Node>();

    int enemyTankSize = 6;
    //定义一个Vector用于存放炸弹
    //说明，当子弹击中坦克时，就加入一个Bomb对象到bombs
    Vector<Bomb> bombs = new Vector<>();
    //定义三张炸弹的图片，用于显示爆炸效果
    Image image1 = null;
    Image image2 = null;
    Image image3 = null;
    //背景音乐
    PlayAudio playAudio = new PlayAudio("D:\\ideaa\\坦克大战音乐\\9924.wav");
    //我方坦克爆炸声
    PlayAudio playAudio1 = new PlayAudio("D:\\ideaa\\坦克大战音乐\\12439.wav");
    //敌方坦克爆炸声
    PlayAudio playAudio2 = new PlayAudio("D:\\ideaa\\坦克大战音乐\\11970.wav");


    public MyPanel(String key) {
        //先判断我们的记录文件是否存在，如果存在就正常，不存在提示只嗯呢该开启新的游戏，key=1
        File file = new File(Recorder.getRecordFile());
        if (file.exists()) {
            nodes = Recorder.getNodesAndEnemyTankRec();
        } else {
            System.out.println("文件不存在，开启新的游戏");
            key = "1";
            try {
                Thread.sleep(2000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        //将本类的坦克数据给了Rector
        Recorder.setEnemyTanks(enemyTanks);
        hero = new Hero(500, 500, 0);
//        com.PlayAudio.setHero(hero);
        //初始化出画出敌人坦克
        switch (key) {
            case "1"://继续上局游戏
                for (int i = 0; i < enemyTankSize; i++) {
                    EnemyTank enemyTank = new EnemyTank(100 * (i + 1), 0, 2);//在这儿就定义了它的位置，画图函数仅仅是画图
                    enemyTank.setDirect(2);
                    //每个坦克敌人对象兜里都应该有一个所有坦克的数据，就这么回事儿
//            enemyTank.setEnemyTanks(enemyTanks,hero);
                    enemyTank.setEnemyTanks(enemyTanks);
                    //在这儿启动敌人坦克的线程
                    new Thread(enemyTank).start();
                    //给敌方坦克加入一颗子弹
                    Shot shot = new Shot(enemyTank.getX() + 20, enemyTank.getY() + 60, enemyTank.getDirect());
                    //加入enemTank的Vector
                    enemyTank.shots.add(shot);
                    //立即启动
                    new Thread(shot).start();
                    //敌方坦克加入集合
                    enemyTanks.add(enemyTank);
                }
                break;
            case "2":
                for (int i = 0; i < nodes.size(); i++) {
                    Node node = nodes.get(i);

                    EnemyTank enemyTank = new EnemyTank(node.getX(), node.getY(), node.getDirect());//在这儿就定义了它的位置，画图函数仅仅是画图
                    enemyTank.setDirect(node.getDirect());
                    //每个坦克敌人对象兜里都应该有一个所有坦克的数据，就这么回事儿
//            enemyTank.setEnemyTanks(enemyTanks,hero);
                    //这儿不对
                    enemyTank.setEnemyTanks(enemyTanks);
                    //在这儿启动敌人坦克的线程
                    new Thread(enemyTank).start();
                    //给敌方坦克加入一颗子弹
                    Shot shot = new Shot(enemyTank.getX() + 20, enemyTank.getY() + 60, enemyTank.getDirect());
                    //加入enemTank的Vector
                    enemyTank.shots.add(shot);
                    //立即启动
                    new Thread(shot).start();
                    //敌方坦克加入集合
                    enemyTanks.add(enemyTank);
                }
                break;
            default:
                System.out.println("你的输入有误：");
        }

        //初始化图片对象
        image1 = Toolkit.getDefaultToolkit().getImage(Panel.class.getResource("/bobm1.jpg"));
//        Image image1 = Toolkit.getDefaultToolkit().getImage("D:\\ideaa\\work1\\TankGame02\\src\\bobm1.jpg");
        image2 = Toolkit.getDefaultToolkit().getImage(Panel.class.getResource("/bobm2.jpg"));
        image3 = Toolkit.getDefaultToolkit().getImage(Panel.class.getResource("/bobm3.jpg"));
        //这里，播放指定的音乐
        PlayAudio playAudio = new PlayAudio("D:\\ideaa\\坦克大战音乐\\9924.wav");
        playAudio.start();
    }

    //编写方法记录我方坦克击毁敌方坦克的数量
    public void showInfo(Graphics g) {
        //设置字体颜色和字体样式
        g.setColor(Color.black);
        Font zt = new Font("宋体", Font.BOLD, 25);
        g.setFont(zt);

        g.drawString("您累计击毁敌方坦克：", 1020, 30);
        this.drawTank(1020, 60, g, 0, 0);
        g.setColor(Color.black);
//        g.drawString(com.Recorder.getAllEnemyTankNum() + "", 1080, 100);

        g.drawString(tankNum() + "", 1080, 100);
    }


    //剩余坦克数量,嘿嘿，自己写的方法！！
    public int tankNum() {
        int i = 0;
        for (int i1 = 0; i1 < enemyTanks.size(); i1++) {
            if (enemyTanks.get(i).isLive) {
                i++;
            }
        }
        return enemyTankSize - i;
    }

    @Override
    public void paint(Graphics g) {
        //看着没用，其实也有用，没有这个的话回话就会重叠
        //应该是会初始化一些参数
        super.paint(g);
        g.setColor(Color.BLACK);
        g.fillRect(0, 0, 1000, 750);
        showInfo(g);
        if (hero != null && hero.isLive) {         //这个if可以让死的子弹不画了，想办法将这个坦克删除
            drawTank(hero.getX(), hero.getY(), g, hero.getDirect(), 1);
        }

        //画出敌人的坦克和子弹
        for (int i = 0; i < enemyTanks.size(); i++) {
            EnemyTank enemyTank = enemyTanks.get(i);
            //先判断当前坦克是否存活
            if (enemyTank.isLive) {//当敌人坦克是存活的话才画出该坦克,仅仅是不打印了！！，他还在那儿，把它在集合中删除
                drawTank(enemyTank.getX(), enemyTank.getY(), g, enemyTank.getDirect(), 0);
                //画出敌人坦克enemyTank的子弹
                for (int j = 0; j < enemyTank.shots.size(); j++) {
                    //取出子弹
                    Shot shot = enemyTank.shots.get(j);
                    //绘制
                    if (shot.isLive) {//如果isLive，子弹活着的时候
                        g.draw3DRect(shot.x, shot.y, 2, 2, false);
                    } else {
                        //移除，
                        enemyTank.shots.remove(shot);
                    }
                }
            }
        }

        //画出hero射出的多颗子弹
        g.setColor(Color.yellow);
        //遍历集合将hero的子弹集合遍历取出绘制所有子弹
        for (int i = 0; i < hero.shots.size(); i++) {
            Shot shot = hero.shots.get(i);
            if (shot != null && shot.isLive) {
//                System.out.println("绘制子弹");
                g.draw3DRect(shot.x, shot.y, 2, 2, false);
            } else {//如果shot对象已经无效，则销毁这个shor对象
                hero.shots.remove(shot);
            }
            //绘制单颗子弹
//            if (hero.shot != null && hero.shot.isLive == true) {
//                System.out.println("子弹被绘制");
//                g.draw3DRect(hero.shot.x, hero.shot.y, 2, 2, false);
////            g.fill3DRect(hero.shot.x, hero.shot.y, 1, 1, false);
//            }
        }

        //如果我们bobms有对象就画出
        for (int i = 0; i < bombs.size(); i++) {
            //取出炸弹
            Bomb bomb = bombs.get(i);
            //根据当前对象的Life去画出对应的图片
            if (bomb.life > 6) {
                g.drawImage(image1, bomb.x, bomb.y, 60, 60, this);
            } else if (bomb.life > 3) {
                g.drawImage(image2, bomb.x, bomb.y, 60, 60, this);
            } else {
                g.drawImage(image3, bomb.x, bomb.y, 60, 60, this);
            }
            //让炸弹的生命值减少
            bomb.lifeDown();
            //如果bomb的生命为0，就从bomb的集合中删除
            if (bomb.life == 0) {
                bombs.remove(bomb);
            }

        }
    }

    public void drawTank(int x, int y, Graphics g, int direct, int type) {
        switch (type) {
            case 0:
                g.setColor(Color.cyan);
                break;
            case 1:
                g.setColor(Color.yellow);
                break;
        }

        switch (direct) {
            case 0:
                g.fill3DRect(x, y, 10, 60, false);
                g.fill3DRect(x + 30, y, 10, 60, false);
                g.fill3DRect(x + 10, y + 10, 20, 40, false);
                g.fillOval(x + 10, y + 20, 20, 20);
                g.drawLine(x + 20, y, x + 20, y + 30);
                break;
            case 1:
                g.fill3DRect(x, y, 60, 10, false);
                g.fill3DRect(x, y + 30, 60, 10, false);
                g.fill3DRect(x + 10, y + 10, 40, 20, false);
                g.fillOval(x + 20, y + 10, 20, 20);
                g.drawLine(x + 30, y + 20, x + 60, y + 20);
                break;
            case 2:
                g.fill3DRect(x, y, 10, 60, false);
                g.fill3DRect(x + 30, y, 10, 60, false);
                g.fill3DRect(x + 10, y + 10, 20, 40, false);
                g.fillOval(x + 10, y + 20, 20, 20);//圆盖
                g.drawLine(x + 20, y + 60, x + 20, y + 30);
                break;
            case 3:
                g.fill3DRect(x, y, 60, 10, false);
                g.fill3DRect(x, y + 30, 60, 10, false);
                g.fill3DRect(x + 10, y + 10, 40, 20, false);
                g.fillOval(x + 20, y + 10, 20, 20);
                g.drawLine(x + 30, y + 20, x, y + 20);
                break;
            default:
                System.out.println("暂时没有处理");
        }
    }

    //如果我们的坦克可以发射多颗子弹，在判断我方子弹是否击中敌人的坦克时，主要将子弹集合取出遍历判断
    public void hitEnemyTank() {
        for (int j = 0; j < hero.shots.size(); j++) {
            Shot shot = hero.shots.get(j);
            //判断是否击中了敌人坦克
            if (shot != null && shot.isLive) {//我的子弹存活的话
                //遍历敌人所有的坦克
                for (int i = 0; i < enemyTanks.size(); i++) {
                    EnemyTank enemyTank = enemyTanks.get(i);
                    hitTank(shot, enemyTank);
                }
            }
        }
    }

    //编写方法判断，判断我方子弹是否击中敌人，如果击中做出响应，生命周期等等参数改变
    // 判断子弹和坦克的关系，传入一个子弹和坦克，比较位置关系是否爆炸
    //修改传入的Tank参数为tank
    public void hitTank(Shot s, EnemyTank enemyTank) {
        //判断s击中坦克
        switch (enemyTank.getDirect()) {
            case 0:
            case 2:
                if (s.x > enemyTank.getX() && s.x < (enemyTank.getX() + 40)
                        && s.y > enemyTank.getY() && s.y < (enemyTank.getY() + 60)) {
                    s.isLive = false;
                    enemyTank.isLive = false;

                    enemyTanks.remove(enemyTank);//在集合中删除坦克，即没有这个效果了
//                    playAudio2.start();    线程这儿不太对劲儿，开启不了
                    //当我方机会一个敌人坦克时，就对allEnemyTankNum值++
                    //创建一个Bomb对象，加入到bomb集合中
                    if (enemyTank instanceof EnemyTank) {
                        Recorder.addAllEnemyTankNum();
                    }
                    Bomb bomb = new Bomb(enemyTank.getX(), enemyTank.getY());
                    bombs.add(bomb);
                    System.out.println("剩余坦克数量为 :" + enemyTanks.size());
                }
                break;
            case 1:
            case 3:
                if (s.x > enemyTank.getX() && s.x < (enemyTank.getX() + 60)
                        && s.y > enemyTank.getY() && s.y < (enemyTank.getY() + 40)) {
                    s.isLive = false;
                    enemyTank.isLive = false;
//                    playAudio1.start();
                    enemyTanks.remove(enemyTank);
//                    playAudio2.start();
                    if (enemyTank instanceof EnemyTank) {
                        Recorder.addAllEnemyTankNum();
                    }
                    Bomb bomb = new Bomb(enemyTank.getX(), enemyTank.getY());
                    bombs.add(bomb);
//                    System.out.println("敌人剩余坦克数量为 :" + enemyTanks.size());
                }
        }
    }


    //判断自己坦克被地敌方击中
    public void hitTank(Shot s, Hero hero) {
        //判断s击中坦克
        switch (hero.getDirect()) {
            case 0:
            case 2:
                if (s.x > hero.getX() && s.x < (hero.getX() + 40)
                        && s.y > hero.getY() && s.y < (hero.getY() + 60)) {
                    s.isLive = false;
                    hero.isLive = false;
//                    playAudio.stop();
                    //在这儿想让背景音乐的线程结束。怎么弄呢
//                    playAudio.sleep();这么也行不通
                    playAudio1.start();

//                    hero=null;
                    //创建一个Bomb对象，加入到bomb集合中
                    Bomb bomb = new Bomb(hero.getX(), hero.getY());
                    bombs.add(bomb);
//                    System.out.println("剩余坦克数量为 :" + enemyTanks.size());
                }
                break;
            case 1:
            case 3:
                if (s.x > hero.getX() && s.x < (hero.getX() + 60)
                        && s.y > hero.getY() && s.y < (hero.getY() + 40)) {
                    s.isLive = false;
                    hero.isLive = false;
                    playAudio1.start();
//                    hero=null;
                    //不能删除，不知为啥
                    Bomb bomb = new Bomb(hero.getX(), hero.getY());
                    bombs.add(bomb);
//                    System.out.println("敌人剩余坦克数量为 :" + enemyTanks.size());
                }
        }
    }


    //编写方法，判断敌人坦克子弹是否击中我们的坦克

    public void hitHero() {
        //遍历所有敌人坦克
        for (int i = 0; i < enemyTanks.size(); i++) {
            //取出敌人坦克
            EnemyTank enemyTank = enemyTanks.get(i);
            //遍历坦克对象的所有子弹
            for (int j = 0; j < enemyTank.shots.size(); j++) {
                //再取出其中的一颗子弹
                Shot shot = enemyTank.shots.get(j);
                //这颗子弹和我们的坦克进行判断
                if (hero.isLive && shot.isLive) {
                    hitTank(shot, hero);
                }
            }
        }
    }


    @Override
    public void keyTyped(KeyEvent e) {

    }

    @Override
    public void keyPressed(KeyEvent e) {
        System.out.print(e.getKeyChar() + "-");//显示按键
        if (e.getKeyCode() == KeyEvent.VK_W) {//按下w键，改变坦克的方向

//            for (int i = 0; i < enemyTanks.size(); i++) {
//                com.EnemyTank enemyTank = enemyTanks.get(i);
//                int direct = enemyTank.getDirect();
//                switch (direct) {
//                    case 0:
//                        if (!(hero.getX() > enemyTank.getX() + 40 && hero.getX() + 40 < enemyTank.getX() && hero.getY() > enemyTank.getY() + 60
//                                && hero.getY() + 60 < enemyTank.getY()&&hero.getY() < 0)) {
//                            hero.setDirect(0);
//                            hero.MoveUp();
//                        }
//                    case 1:
//                        if (!(hero.getX() > enemyTank.getX() + 60 && hero.getX() + 40 < enemyTank.getX() && hero.getY() > enemyTank.getY() + 40
//                                && hero.getY() + 60 < enemyTank.getY()&&hero.getY() < 0)) {
//                            hero.setDirect(0);
//                            hero.MoveUp();
//                        }
//                    case 2:
//                        if (!(hero.getX() > enemyTank.getX() + 40 && hero.getX() + 40 < enemyTank.getX() && hero.getY() > enemyTank.getY() + 60
//                                && hero.getY() + 60 < enemyTank.getY()&&hero.getY() < 0)) {
//                            hero.setDirect(0);
//                            hero.MoveUp();
//                        }
//                    case 3:
//                        if (!(hero.getX() > enemyTank.getX() + 60 && hero.getX() + 40 < enemyTank.getX() && hero.getY() > enemyTank.getY() + 40
//                                && hero.getY() + 60 < enemyTank.getY()&&hero.getY() < 0)) {
//                            hero.setDirect(0);
//                            hero.MoveUp();
//                        }
//                }
//            }

            hero.setDirect(0);
            if (hero.getY() > 0) {
                hero.MoveUp();
            }
        }
        if (e.getKeyCode() == KeyEvent.VK_S) {
            hero.setDirect(2);
            if (hero.getY() + 60 < 750) {
                hero.MoveDown();
            }
        }

        if (e.getKeyCode() == KeyEvent.VK_A) {
            hero.setDirect(3);
            if (hero.getX() > 0) {
                hero.MoveLeft();

            }
        }
        if (e.getKeyCode() == KeyEvent.VK_D) {
            hero.setDirect(1);
            if (hero.getX() + 60 < 1000) {
                hero.MoveRight();
            }
        }
        if (e.getKeyCode() == KeyEvent.VK_J) {
            //子弹是一个线程，为了让自己只能放一颗子弹
//            if (hero.shot == null || !hero.shot.isLive) {
//                hero.shotEnemyTank();
//            }
            //发射子弹,得判断子弹坦克是否活着
            if (hero.isLive) {
                hero.shotEnemyTank();
            }


        }
        repaint();
    }

    @Override
    public void keyReleased(KeyEvent e) {

    }

    @Override
    public void run() {//每隔一定时间自己重绘区域,子弹就移动起来了
        //bug还是很多的，这个bug不太会改，可能与电脑有点问题
        try {//这儿不休眠，第一颗   子弹没有效果
            Thread.sleep(50);       //
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        while (true) {
            try {
                Thread.sleep(10);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            //我们是否击中了敌人的坦克
            hitEnemyTank();
            //敌人坦克是否击中我们
            hitHero();
            System.out.println("剩余坦克数量为 :" + enemyTanks.size());
            this.repaint();
            //这个线程可一直没停
        }
    }
}
